package org.nicocube.airain.app.client;

import java.util.List;
import java.util.Map;

import org.nicocube.airain.app.client.domain.GameCharacter;
import org.nicocube.airain.app.client.table.Item;
import org.nicocube.airain.app.client.table.TableHeader;
import org.nicocube.airain.app.client.table.TableOfItem;
import org.nicocube.airain.app.client.ui.AirainMessager;

import com.google.gwt.core.client.EntryPoint;
import com.google.gwt.core.client.GWT;
import com.google.gwt.event.dom.client.ClickEvent;
import com.google.gwt.event.dom.client.ClickHandler;
import com.google.gwt.i18n.client.Constants;
import com.google.gwt.user.client.rpc.AsyncCallback;
import com.google.gwt.user.client.ui.Button;
import com.google.gwt.user.client.ui.DecoratorPanel;
import com.google.gwt.user.client.ui.DialogBox;
import com.google.gwt.user.client.ui.HasHorizontalAlignment;
import com.google.gwt.user.client.ui.HorizontalPanel;
import com.google.gwt.user.client.ui.Image;
import com.google.gwt.user.client.ui.Label;
import com.google.gwt.user.client.ui.RootPanel;
import com.google.gwt.user.client.ui.VerticalPanel;
import com.google.gwt.user.client.ui.Widget;

/**
 * Entry point classes define <code>onModuleLoad()</code>.
 */
public class AirainApp implements EntryPoint {

	public interface I18nConstants extends Constants{
		@DefaultStringMapValue({"M","Male","F","Female"})
		Map<String, String> genders();

		@DefaultStringValue("Please wait while loading.")
		String waitLoading();

		@DefaultStringValue("Name")
		String headerNameLabel();

		@DefaultStringValue("Gender")
		String headerGenderLabel();

		@DefaultStringValue("Birth date")
		String headerBirthDateLabel();

		@DefaultStringValue("Delete")
		String iconDeleteLabel();
		
		@DefaultStringValue("Play")
		String iconPlayLabel();
	}

	/**
	 * Create a remote service proxy to talk to the server-side Greeting service.
	 */
	private final GCServiceAsync gcService = GWT.create(GCService.class);

	private AirainMessager messenger;

	private TableOfItem flexTable;

	private I18nConstants constants;

	/**
	 * This is the entry point method.
	 */
	public void onModuleLoad() {
		constants = GWT.create(I18nConstants.class);
		
		messenger = new AirainMessager();

		messenger.show(constants.waitLoading());

		flexTable = new TableOfItem(
				new TableHeader()
				.addCol(constants.headerNameLabel())
				.addCol(constants.headerGenderLabel())
				.addCol(constants.headerBirthDateLabel())
				.addCol()
				.addCol()
		).noData("No Data ...");

		gcService.getList(new AsyncCallback<List<GameCharacter>>() {
			@Override
			public void onFailure(Throwable caught) {
				messenger.show("Error while loading.");
			}
			@Override
			public void onSuccess(List<GameCharacter> result) {
				messenger.hide();

				if (result.size() > 0) {
					for (final GameCharacter gc : result) {
						addRow(flexTable, gc);
					}
				}
				launchUI();
			}			
		});

	}

	private void launchUI() {	

		final DecoratorPanel dp0 = new DecoratorPanel();

		final VerticalPanel vp0 = new VerticalPanel();

		dp0.add(vp0);

		vp0.add(flexTable.render());

		Widget w = new CreateGameCharacterPanel(gcService,messenger) {
			@Override
			protected void onCreate(GameCharacter result) {
				addRow(flexTable, result);
				flexTable.render();
			}
		};
		vp0.add(w);

		RootPanel.get().add(dp0);

	}

	private void addRow(final TableOfItem flexTable,final GameCharacter gc) {
		Image deleteButton = new Image("icon-delete.png");
		deleteButton.setTitle(constants.iconDeleteLabel());
		Image playButton = new Image("icon-play.png");
		playButton.setTitle(constants.iconPlayLabel());
		
		final Item iv = new Item()
			.setIdent(gc.getName())
			.addValue(constants.genders().get(String.valueOf(gc.getGender())))
			.addValue(String.valueOf(gc.getBirthDate()))
			.addWidget(deleteButton)
			.addWidget(playButton);
		
		flexTable.addRow(iv);
		
		deleteButton.addClickHandler(new ClickHandler() {
			@Override
			public void onClick(ClickEvent event) {
				final DialogBox db = new DialogBox();
				db.setText("Delete confirmation");
				VerticalPanel dialogContents = new VerticalPanel();

				dialogContents.add(new Label("Are you sure you want to delete character named "+gc.getName()+" ?"));

				Button yesButton = new Button("yes",
						new ClickHandler() {
					public void onClick(ClickEvent event) {
						db.hide(true);
						gcService.delete(gc, new AsyncCallback<Boolean>() {
							@Override
							public void onFailure(Throwable caught) {
								messenger.show("Error while deleting.");
							}
							@Override
							public void onSuccess(Boolean result) {
								if (result) {
									flexTable.delRow(iv);
									flexTable.render();
								}
							}
						});
					}
				});
				
				Button noButton = new Button("no",
						new ClickHandler() {
					public void onClick(ClickEvent event) {
						db.hide(true);
					}
				});

				HorizontalPanel hp = new HorizontalPanel();

				hp.add(yesButton);
				hp.add(noButton);
				dialogContents.add(hp);
				dialogContents.setCellHorizontalAlignment(hp, HasHorizontalAlignment.ALIGN_CENTER);
				
				db.add(dialogContents);
				db.center();
				db.show();
			}
		});
	}

}
